package com.neusoft.bizcore.license.utils;

import java.net.InetAddress;
import java.net.NetworkInterface;
import java.net.SocketException;
import java.util.ArrayList;
import java.util.Enumeration;
import java.util.List;

import com.neusoft.bizcore.license.bean.LicenseCheckBean;

import lombok.extern.slf4j.Slf4j;

/**
 * 获取服务器信息
 *
 * @author sunchf
 * @date 2019年11月7日 上午9:14:34
 */
@Slf4j
public abstract class AbstractServerInfo {

    /**
     * 组装需要额外校验的License参数
     *
     * @return
     */
    public LicenseCheckBean getServerInfos() {
        final LicenseCheckBean result = new LicenseCheckBean();

        try {
            result.setIpAddress(this.getIpAddress());
            result.setMacAddress(this.getMacAddress());
            result.setCpuSerial(this.getCPUSerial());
            result.setMainBoardSerial(this.getMainBoardSerial());
        } catch (final Exception e) {
            AbstractServerInfo.log.error("获取服务器硬件信息失败", e);
        }

        return result;
    }

    /**
     * 获取IP地址
     *
     * @return
     * @throws Exception
     */
    protected abstract List<String> getIpAddress() throws Exception;

    /**
     * 获取Mac地址
     *
     * @return
     * @throws Exception
     */
    protected abstract List<String> getMacAddress() throws Exception;

    /**
     * 获取CPU序列号
     *
     * @return
     * @throws Exception
     */
    protected abstract String getCPUSerial() throws Exception;

    /**
     * 获取主板序列号
     *
     * @return
     * @throws Exception
     */
    protected abstract String getMainBoardSerial() throws Exception;

    /**
     * 获取当前服务器所有符合条件的InetAddress
     *
     * @return
     * @throws Exception
     */
    protected List<InetAddress> getLocalAllInetAddress() throws Exception {
        final List<InetAddress> result = new ArrayList<>(4);

        for (final Enumeration<NetworkInterface> networkInterfaces =
                NetworkInterface.getNetworkInterfaces(); networkInterfaces
                        .hasMoreElements();) {
            final NetworkInterface iface = networkInterfaces.nextElement();

            for (final Enumeration<InetAddress> inetAddresses = iface.getInetAddresses(); inetAddresses
                    .hasMoreElements();) {
                final InetAddress inetAddress = inetAddresses.nextElement();

                //排除LoopbackAddress、LinkLocalAddress、MulticastAddress类型的IP地址
                if (!inetAddress.isLoopbackAddress()
                        && !inetAddress.isLinkLocalAddress() && !inetAddress.isMulticastAddress()) {
                    result.add(inetAddress);
                }
            }
        }

        return result;
    }

    /**
     * 获取某个网络接口的Mac地址
     *
     * @param inetAddress
     * @return
     */
    protected String getMacByInetAddress(InetAddress inetAddress) {
        try {
            final byte[] mac = NetworkInterface.getByInetAddress(inetAddress).getHardwareAddress();
            final StringBuffer stringBuffer = new StringBuffer();

            for (int i = 0; i < mac.length; i++) {
                if (i != 0) {
                    stringBuffer.append("-");
                }

                //将十六进制byte转化为字符串
                final String temp = Integer.toHexString(mac[i] & 0xff);
                if (temp.length() == 1) {
                    stringBuffer.append("0" + temp);
                } else {
                    stringBuffer.append(temp);
                }
            }

            return stringBuffer.toString().toUpperCase();
        } catch (final SocketException e) {
            AbstractServerInfo.log.error("", e);
        }

        return null;
    }

}
